package com.dnxh.config;

import cn.hutool.setting.dialect.Props;
import org.apache.shiro.mgt.DefaultSessionStorageEvaluator;
import org.apache.shiro.mgt.DefaultSubjectDAO;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import javax.servlet.Filter;
import java.util.*;

/**
 * @Author 枳湫
 * @Time 2022/4/6 11:01
 * @Describe Basic_jar
 **/
@Configuration
public class ShiroConfig {
	
	private static final List<String> urls;
	private static final String       JWT  = "jwt";
	private static final String       ANON = "anon";
	
	static {
		synchronized (ShiroConfig.class) {
			Props props = new Props ("classpath:/config/ignore_url.properties");
			props.load ();
			urls = Arrays.asList (props.getStr ("IGNORE_URLS").split (","));
		}
	}
	
	@Bean
	@ConditionalOnMissingBean
	public DefaultAdvisorAutoProxyCreator defaultAdvisorAutoProxyCreator () {
		DefaultAdvisorAutoProxyCreator defaultApp = new DefaultAdvisorAutoProxyCreator ();
		defaultApp.setProxyTargetClass (true);
		return defaultApp;
	}
	
	@Bean
	public ShiroFilterFactoryBean factoryBean (SecurityManager securityManager) {
		ShiroFilterFactoryBean shiroFilterFactoryBean = new ShiroFilterFactoryBean ();
		shiroFilterFactoryBean.setUnauthorizedUrl ("/unauthorized/无权限");
		Map<String, Filter> filterMap = new LinkedHashMap<> (1);
		filterMap.put (JWT, new JwtFilter ());
		shiroFilterFactoryBean.setFilters (filterMap);
		shiroFilterFactoryBean.setSecurityManager (securityManager);
		Map<String, String> map = new HashMap<> (1200);
		map.put ("/**", JWT);
		for (String url : urls) {
			map.put (url, ANON);
		}
		shiroFilterFactoryBean.setFilterChainDefinitionMap (map);
		return shiroFilterFactoryBean;
	}
	
	@Bean
	public CustomRealm myShiroRealm () {
		return new CustomRealm ();
	}
	
	@Bean
	public SecurityManager securityManager () {
		DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager ();
		securityManager.setRealm (myShiroRealm ());
		DefaultSubjectDAO subjectDAO = new DefaultSubjectDAO ();
		DefaultSessionStorageEvaluator defaultSessionStorageEvaluator = new DefaultSessionStorageEvaluator ();
		defaultSessionStorageEvaluator.setSessionStorageEnabled (false);
		subjectDAO.setSessionStorageEvaluator (defaultSessionStorageEvaluator);
		securityManager.setSubjectDAO (subjectDAO);
		return securityManager;
	}
	
	@Bean
	public AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor (SecurityManager securityManager) {
		AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor =
				new AuthorizationAttributeSourceAdvisor ();
		authorizationAttributeSourceAdvisor.setSecurityManager (securityManager);
		return authorizationAttributeSourceAdvisor;
	}
}